using System.Collections.Generic;
using AudioStudio;
using Gameplay.PVE.Data;
using Gameplay.PVE.Effect;
using Gameplay.PVE.Entity;
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.Rendering.Universal;

namespace Gameplay.PVE.Utils
{
    public class PveEffectManager
    {
        private static PveEffectManager instance;
        
        public static PveEffectManager Instance
        {
            get
            {
                if (instance == null)
                {
                    instance = new PveEffectManager();
                }
                return instance;
            }
        }
        
        public BlackScreenEffect blackScreenEffect;

        private struct PveEffect
        {
            public int effectId;
            public GameObject effect;
            public PveEffectController controller;
            public bool useStartForward;
            public Vector3 startForward;
            public float autoDestroyTime;
            public PveResourceManager.EPveResType type;
        }
        
        private List<PveEffect> playingEffectList = new List<PveEffect>();
        
        public void Initialize()
        {
            blackScreenEffect = new BlackScreenEffect();
            blackScreenEffect.Initialize();
        }

        private float nearClip;
        
        
        
        public void ShowBlackScreen()
        {
            PveCameraManager.Instance.ChangeRpgCameraPostProcess(false);
            //启用摄像机的depthtexture
            PveCameraManager.Instance.ChangeDepthTextureEnabled(true);
            blackScreenEffect.Show();
        }

        public void HideBlackScreen()
        {
            PveCameraManager.Instance.ChangeRpgCameraPostProcess(true);
            //关闭摄像机的depthtexture
            PveCameraManager.Instance.ChangeDepthTextureEnabled(false);
            blackScreenEffect.Hide();
        }

        public void Update()
        {
            for (int i = 0; i < playingEffectList.Count; i++)
            {
                var effect = playingEffectList[i];
                if (TimeManager.logicTime >  effect.autoDestroyTime)
                {
                    PveResourceManager.RecoverResource(effect.effect, effect.type, effect.effectId);
                    playingEffectList.RemoveAt(i);
                    i--;
                }
                else
                {
                    if (effect.useStartForward && effect.effect != null)
                    {
                        effect.effect.transform.forward = effect.startForward;
                    }
                }
            }
            
        }

        public void FixedUpdate()
        {
            blackScreenEffect?.Update();
        }

        public void Pause()
        {
            for (int i = 0; i < playingEffectList.Count; i++)
            {
                var pveEffectController = playingEffectList[i].controller;
                if (pveEffectController != null)
                {
                    pveEffectController.Pause();
                }
            }
        }

        public void Resume()
        {
            for (int i = 0; i < playingEffectList.Count; i++)
            {
                var pveEffectController = playingEffectList[i].controller;
                if (pveEffectController != null)
                {
                    pveEffectController.Resume();
                }
            }
        }
        
        public void ChangeBlackScreenAlpha(float alpha, float time)
        {
            blackScreenEffect?.ChangeAlpha(alpha,time);
        }

        //丢给外界管理
        public GameObject PlayEffect(int effectId,UnitBase unit)
        {
            var position = unit.Data.position;
            var forward = unit.Data.forward;
            var config = PveUtils.GetRpgEffectConfig(effectId);
            if (config != null)
            {
                Transform parent = null;
                if (config.set_parent == 1)
                {
                    parent = unit.gameObject.transform;
                }

                if (config.parent_index >= 0 && unit.Data.buffEffectPoints != null &&
                    unit.Data.buffEffectPoints.Count > config.parent_index)
                {
                    parent = unit.Data.buffEffectPoints[config.parent_index];
                    position = parent.position;
                }
                return PlayEffect2(effectId, position, forward, 0, parent);
            }
            return null;
        }
        
        // 自己管理特效的生命
        public void PlayEffect(int effectId, Vector3 position, Vector3 forward, float autoDestroyTime = 5f,
            float scale = 0, Transform parent = null)
        {
            PlayEffectByType(PveResourceManager.EPveResType.SkillEffect, effectId, position, forward, autoDestroyTime,
                scale, parent);
        }

        // 丢给外界管理
        public GameObject PlayEffect2(int effectId, Vector3 position, Vector3 forward, float scale = 0,
            Transform parent = null)
        {
            return PlayEffectByType(PveResourceManager.EPveResType.SkillEffect, effectId, position, forward, scale,
                parent);
        }

        public int GetEffectNum()
        {
            return playingEffectList.Count;
        }
        
        public void PlayEffectByType(PveResourceManager.EPveResType type, int effectId, Vector3 position,
            Vector3 forward, float autoDestroyTime = 5f, float scale = 0, Transform parent = null)
        {
            if(!PveFlyTextManager.Instance.showEffect) return;
            var effect = PlayEffectByType(type, effectId, position, forward, scale, parent);
            if (effect)
            {
                float time = 2;
                var controller = effect.GetComponent<PveEffectController>();
                if (controller != null)
                {
                    controller.Init();
                    time = controller.IsLoop
                        ? TimeManager.logicTime + autoDestroyTime
                        : TimeManager.logicTime + controller.PlayTime;
                }
                var config = PveUtils.GetRpgEffectConfig(effectId);
                bool useStartForward = config.set_parent == 2;
                Vector3 startForward = Vector3.zero;
                if (useStartForward)
                {
                    startForward = effect.transform.forward;
                }
                
                playingEffectList.Add(new PveEffect
                {
                    type = type,
                    effectId = effectId,
                    effect = effect,
                    autoDestroyTime = time,
                    controller = controller,
                    startForward = startForward,
                    useStartForward = useStartForward,
                });
            }
                
        }

        private GameObject PlayEffectByType(PveResourceManager.EPveResType type, int effectId, Vector3 position,
            Vector3 forward, float scale = 0, Transform parent = null)
        {
            if(!PveFlyTextManager.Instance.showEffect) return null;
            var effectConfig = PveUtils.GetRpgEffectConfig(effectId);
            if (effectConfig == null)
            {
                return null;
            }
            var effect = PveResourceManager.GetResource(type, effectConfig.res_id_h);
            if (effect != null)
            {
                if (effectConfig.set_parent > 0 && parent != null)
                {
                    effect.transform.SetParent(parent);
                    effect.transform.localEulerAngles = Vector3.zero;
                }
                else
                {
                    effect.transform.SetParent(PveScene.pveRootTrans);
                }
                effect.transform.position = position;
                effect.transform.SetActive(true);
                if (forward != Vector3.zero)
                {
                    effect.transform.forward = forward;
                }

                var offset =
                    PveUtils.GetRandomVector3(effectConfig.position_offset_min, effectConfig.position_offset_max);
                var angleOffset =
                    PveUtils.GetRandomVector3(effectConfig.angle_offset_min, effectConfig.angle_offset_max);

                effect.transform.position += offset;
                effect.transform.localEulerAngles += angleOffset;
                                
                float extraScale = Random.Range(effectConfig.scale_min, effectConfig.scale_max);
                if (extraScale != 0)
                {
                    scale = scale * extraScale;
                }
                if (scale != 0)
                {
                    effect.transform.localScale = new Vector3(scale, scale, scale);
                }
                else
                {
                    effect.transform.localScale = new Vector3(1,1,1);
                }

                if (!string.IsNullOrEmpty(effectConfig.sound_name))
                {
                    if (effectConfig.sound_delay == 0)
                    {
                        AudioManager.PlaySound(effectConfig.sound_name);
                    }
                    else
                    {
                        TimeManager.Instance.DelayCall((int)(effectConfig.sound_delay * 1000),
                            () => { AudioManager.PlaySound(effectConfig.sound_name); });
                    }
                }
            }
            
            return effect;
        }

        public void ClearStage()
        {
            for (int i = 0; i < playingEffectList.Count; i++)
            {
                PveResourceManager.RecoverResource(playingEffectList[i].effect,playingEffectList[i].type,playingEffectList[i].effectId);
            }
            playingEffectList.Clear();
        }
        
        public void Dispose()
        {
            ClearStage();
            instance = null;
        }
    }
}
